package com.sz.virtualbank.service.bankcard.impl;

import com.sz.virtualbank.common.exception.BusinessException;
import com.sz.virtualbank.dao.entity.BankCard;
import com.sz.virtualbank.dao.entity.User;
import com.sz.virtualbank.dao.mapper.BankCardMapper;
import com.sz.virtualbank.dao.mapper.UserMapper;
import com.sz.virtualbank.service.bankcard.BankCardService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;
import java.util.regex.Pattern;

/**
 * 银行卡服务实现类
 * 
 * @author Claude
 */
@Service
@Slf4j
public class BankCardServiceImpl implements BankCardService {

    @Autowired
    private BankCardMapper bankCardMapper;
    
    @Autowired
    private UserMapper userMapper;
    
    // 银行卡号正则表达式（简化版）
    private static final Pattern CARD_NUMBER_PATTERN = Pattern.compile("^\\d{16,19}$");
    
    // 有效期格式：MM/YY
    private static final Pattern EXPIRE_DATE_PATTERN = Pattern.compile("^(0[1-9]|1[0-2])/\\d{2}$");
    
    // CVV格式：3-4位数字
    private static final Pattern CVV_PATTERN = Pattern.compile("^\\d{3,4}$");

    @Override
    @Transactional(rollbackFor = Exception.class)
    public BankCard addBankCard(BankCard bankCard) {
        // 参数校验
        if (bankCard == null || bankCard.getUserId() == null) {
            throw new BusinessException("参数不能为空");
        }
        
        if (StringUtils.isBlank(bankCard.getCardNumber()) || !CARD_NUMBER_PATTERN.matcher(bankCard.getCardNumber()).matches()) {
            throw new BusinessException("银行卡号格式不正确");
        }
        
        if (StringUtils.isBlank(bankCard.getBankName())) {
            throw new BusinessException("银行名称不能为空");
        }
        
        if (StringUtils.isBlank(bankCard.getCardholderName())) {
            throw new BusinessException("持卡人姓名不能为空");
        }
        
        if (StringUtils.isBlank(bankCard.getBindPhone())) {
            throw new BusinessException("绑定手机号不能为空");
        }
        
        // 信用卡必须填写有效期和安全码
        if (bankCard.getCardType() == 2) {
            if (StringUtils.isBlank(bankCard.getExpireDate()) || !EXPIRE_DATE_PATTERN.matcher(bankCard.getExpireDate()).matches()) {
                throw new BusinessException("有效期格式不正确（MM/YY）");
            }
            
            if (StringUtils.isBlank(bankCard.getCvv()) || !CVV_PATTERN.matcher(bankCard.getCvv()).matches()) {
                throw new BusinessException("安全码格式不正确（3-4位数字）");
            }
        }
        
        // 检查用户是否存在
        User user = userMapper.selectById(bankCard.getUserId());
        if (user == null) {
            throw new BusinessException("用户不存在");
        }
        
        // 检查卡号是否已存在
        BankCard existingCard = bankCardMapper.selectByCardNumber(bankCard.getCardNumber());
        if (existingCard != null) {
            throw new BusinessException("该银行卡已被绑定");
        }
        
        // 验证银行卡有效性
        boolean valid = validateBankCard(
            bankCard.getCardNumber(), 
            bankCard.getCardholderName(), 
            bankCard.getExpireDate(), 
            bankCard.getCvv()
        );
        
        if (!valid) {
            throw new BusinessException("银行卡信息验证失败");
        }
        
        // 如果是设置为默认卡，则先将其他卡设置为非默认
        if (bankCard.getIsDefault() != null && bankCard.getIsDefault() == 1) {
            bankCardMapper.resetDefaultCards(bankCard.getUserId());
        }
        
        // 设置初始值
        bankCard.setStatus(1); // 正常
        bankCard.setCreateTime(LocalDateTime.now());
        bankCard.setUpdateTime(LocalDateTime.now());
        
        // 添加银行卡
        bankCardMapper.insert(bankCard);
        
        // 处理返回值，脱敏卡号
        bankCard.setCardNumber(maskCardNumber(bankCard.getCardNumber()));
        
        return bankCard;
    }

    @Override
    public List<BankCard> getBankCardList(Long userId) {
        List<BankCard> cards = bankCardMapper.selectByUserId(userId);
        
        // 卡号脱敏处理
        for (BankCard card : cards) {
            card.setCardNumber(maskCardNumber(card.getCardNumber()));
        }
        
        return cards;
    }

    @Override
    public BankCard getBankCardDetail(Long id, Long userId) {
        BankCard bankCard = bankCardMapper.selectById(id);
        
        // 验证银行卡是否存在及归属权
        if (bankCard == null || !bankCard.getUserId().equals(userId)) {
            throw new BusinessException("银行卡不存在或不属于当前用户");
        }
        
        // 卡号脱敏处理
        bankCard.setCardNumber(maskCardNumber(bankCard.getCardNumber()));
        
        return bankCard;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean setDefaultCard(Long id, Long userId) {
        BankCard bankCard = bankCardMapper.selectById(id);
        
        // 验证银行卡是否存在及归属权
        if (bankCard == null || !bankCard.getUserId().equals(userId)) {
            throw new BusinessException("银行卡不存在或不属于当前用户");
        }
        
        // 将其他银行卡设置为非默认
        bankCardMapper.resetDefaultCards(userId);
        
        // 设置当前银行卡为默认
        return bankCardMapper.setDefaultCard(id, userId) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean deleteBankCard(Long id, Long userId) {
        BankCard bankCard = bankCardMapper.selectById(id);
        
        // 验证银行卡是否存在及归属权
        if (bankCard == null || !bankCard.getUserId().equals(userId)) {
            throw new BusinessException("银行卡不存在或不属于当前用户");
        }
        
        // 默认银行卡不能删除
        if (bankCard.getIsDefault() == 1) {
            throw new BusinessException("不能删除默认银行卡");
        }
        
        return bankCardMapper.deleteById(id) > 0;
    }

    @Override
    public BankCard getDefaultCard(Long userId) {
        BankCard defaultCard = bankCardMapper.selectDefaultCard(userId);
        
        if (defaultCard != null) {
            // 卡号脱敏处理
            defaultCard.setCardNumber(maskCardNumber(defaultCard.getCardNumber()));
        }
        
        return defaultCard;
    }

    @Override
    public boolean validateBankCard(String cardNumber, String cardholderName, String expireDate, String cvv) {
        // 实际应用中，这里应该调用银行或第三方支付接口进行验证
        // 本示例中，只做简单的格式校验
        
        // 校验卡号格式
        if (StringUtils.isBlank(cardNumber) || !CARD_NUMBER_PATTERN.matcher(cardNumber).matches()) {
            return false;
        }
        
        // 如果有有效期和安全码，进行校验
        if (StringUtils.isNotBlank(expireDate)) {
            if (!EXPIRE_DATE_PATTERN.matcher(expireDate).matches()) {
                return false;
            }
            
            // 检查有效期是否过期
            String[] parts = expireDate.split("/");
            int month = Integer.parseInt(parts[0]);
            int year = Integer.parseInt(parts[1]) + 2000; // 假设是20xx年
            
            LocalDateTime now = LocalDateTime.now();
            if (year < now.getYear() || (year == now.getYear() && month < now.getMonthValue())) {
                return false;
            }
        }
        
        if (StringUtils.isNotBlank(cvv) && !CVV_PATTERN.matcher(cvv).matches()) {
            return false;
        }
        
        return true;
    }
    
    /**
     * 卡号脱敏处理
     *
     * @param cardNumber 卡号
     * @return 脱敏后的卡号
     */
    private String maskCardNumber(String cardNumber) {
        if (StringUtils.isBlank(cardNumber)) {
            return cardNumber;
        }
        
        int length = cardNumber.length();
        if (length <= 8) {
            return cardNumber;
        }
        
        // 保留前4后4，中间使用*代替
        String prefix = cardNumber.substring(0, 4);
        String suffix = cardNumber.substring(length - 4);
        
        return prefix + "****" + suffix;
    }
}
